import Parser from 'tree-sitter';
import Java from 'tree-sitter-java';
import Kotlin from 'tree-sitter-kotlin';
import { logger } from '../utils/logger';
import { ExtractionTask, ExtractionResult } from '../types';
import {
  Translation,
  TranslationInfo,
  TranslationContext,
  TranslationOccurrence,
  TranslationStatistics,
  TRANSLATION_METHODS,
  NON_TRANSLATION_STRINGS,
  BUNDLE_KEY_PREFIXES,
  TRANSLATION_KEY_PATTERN,
  R_STRING_PATTERN
} from '../types/translation';
import * as fs from 'fs';
import * as path from 'path';
import * as chardet from 'chardet';
import * as iconv from 'iconv-lite';
import { EventEmitter } from 'events';
import { TranslationPackLoader } from '../services/TranslationPackLoader';

// 解析器配置接口
export interface JavaParserOptions {
  includeComments: boolean;
  extractContext: boolean;
  maxDepth: number;
  ignorePatterns: string[];
  keyPatterns: string[];
  valuePatterns: string[];
  encoding?: string;
  maxFileSize?: number;
  parseTimeout?: number;
  skipComplexStructures?: boolean;
  fallbackToRegex?: boolean;
  customRules?: Array<{
    name: string;
    pattern: string;
    action: 'include' | 'exclude' | 'transform';
  }>;
}

export class JavaParser extends EventEmitter {
  private parser: Parser;
  private definedTranslationKeys: Set<string> = new Set();
  private usedTranslationKeys: Set<string> = new Set();
  private moduleMap: Map<string, Set<string>> = new Map();
  private processedReferences: Set<string> = new Set();
  private methodUsage: Map<string, number> = new Map();
  private options: JavaParserOptions;
  private translationPackLoader: TranslationPackLoader | null = null;
  private analysisResults: any = {};

  constructor(options?: Partial<JavaParserOptions>) {
    super(); // 初始化 EventEmitter
    
    // 默认选项
    this.options = {
      includeComments: true,
      extractContext: true,
      maxDepth: 70,
      ignorePatterns: [],
      keyPatterns: [],
      valuePatterns: [],
      encoding: 'auto',
      maxFileSize: 1024 * 1024, // 1MB
      parseTimeout: 5000, // 5秒
      skipComplexStructures: true,
      fallbackToRegex: true,
      ...options
    };

    // 初始化解析器
    this.parser = new Parser();
    
    try {
      // 默认设置 Java 语言（后续会根据文件扩展名动态切换）
      this.parser.setLanguage(Java);
      // 使用 null 作为 logger
      this.parser.setLogger(null);
      
      // 初始化基本的定义翻译键
      this.initDefinedTranslationKeys();
    } catch (error) {
      logger.error('解析器初始化失败', { 错误: error instanceof Error ? error.message : String(error) });
      throw new Error('Failed to initialize parser');
    }

    logger.info('解析器初始化成功', { 选项: this.options });
  }

  /**
   * 初始化基础的定义翻译键集合
   */
  private initDefinedTranslationKeys(): void {
    // 添加一些基本的已定义翻译键示例
    // 这些通常会从项目的资源文件或配置中加载
    const basicDefinedKeys = [
      "app_name",
      "ok",
      "cancel",
      "yes",
      "no",
      "submit",
      "error",
      "success",
      "loading",
      "retry",
      "welcome",
      "login",
      "register",
      "logout",
      "email",
      "password",
      "username",
      "home",
      "profile",
      "settings"
    ];
    
    // 将这些基本定义的键添加到集合中
    basicDefinedKeys.forEach(key => this.definedTranslationKeys.add(key));
    
    logger.info('初始化翻译键定义', { 
      初始键数量: this.definedTranslationKeys.size
    });
  }

  /**
   * 加载资源文件中定义的翻译键
   * @param resourceDirs 资源目录列表
   */
  public async loadDefinedTranslationKeys(resourceDirs: string[]): Promise<void> {
    for (const dir of resourceDirs) {
      try {
        await this.scanResourceDir(dir);
      } catch (error) {
        logger.error('扫描资源目录失败', { 
          目录: dir, 
          错误: error instanceof Error ? error.message : String(error) 
        });
      }
    }
    
    logger.info('加载翻译键定义完成', { 
      已定义键总数: this.definedTranslationKeys.size
    });
  }
  
  /**
   * 扫描资源目录，加载定义的翻译键
   * @param dirPath 资源目录路径
   */
  private async scanResourceDir(dirPath: string): Promise<void> {
    // 检查目录是否存在
    if (!fs.existsSync(dirPath)) {
      logger.warn('资源目录不存在', { 目录: dirPath });
      return;
    }
    
    try {
      // 递归读取目录下的所有文件
      const scanDir = async (dir: string) => {
        const files = await fs.promises.readdir(dir, { withFileTypes: true });
        
        for (const file of files) {
          const filePath = path.join(dir, file.name);
          
          if (file.isDirectory()) {
            // 递归扫描子目录
            await scanDir(filePath);
          } else if (file.isFile()) {
            // 处理资源文件
            const ext = path.extname(file.name).toLowerCase();
            
            if (ext === '.xml') {
              // 处理 Android 资源文件
              await this.processAndroidResourceFile(filePath);
            } else if (ext === '.properties' || ext === '.strings') {
              // 处理 Java/iOS 属性文件
              await this.processPropertiesFile(filePath);
            } else if (ext === '.json') {
              // 处理 JSON 资源文件
              await this.processJsonResourceFile(filePath);
            }
          }
        }
      };
      
      await scanDir(dirPath);
      
      logger.info('资源目录扫描完成', { 
        目录: dirPath, 
        已定义键数量: this.definedTranslationKeys.size
      });
    } catch (error) {
      logger.error('扫描资源目录过程出错', { 
        目录: dirPath, 
        错误: error instanceof Error ? error.message : String(error)
      });
    }
  }
  
  /**
   * 处理 Android 资源文件 (strings.xml)
   * @param filePath 文件路径
   */
  private async processAndroidResourceFile(filePath: string): Promise<void> {
    try {
      // 仅处理 strings.xml 文件
      if (!filePath.includes('strings.xml')) {
        return;
      }
      
      const content = await this.readJavaFile(filePath);
      // 使用简单的正则表达式提取字符串键
      const matches = content.matchAll(/<string\s+name="([^"]+)".*?>[\s\S]*?<\/string>/g);
      
      let keysCount = 0;
      for (const match of matches) {
        if (match[1]) {
          this.definedTranslationKeys.add(match[1]);
          keysCount++;
        }
      }
      
      logger.info('处理Android资源文件', { 
        文件: filePath, 
        添加键数: keysCount
      });
    } catch (error) {
      logger.warn('处理Android资源文件失败', { 
        文件: filePath, 
        错误: error instanceof Error ? error.message : String(error)
      });
    }
  }
  
  /**
   * 处理属性文件 (.properties, .strings)
   * @param filePath 文件路径
   */
  private async processPropertiesFile(filePath: string): Promise<void> {
    try {
      const content = await this.readJavaFile(filePath);
      const lines = content.split('\n');
      
      let keysCount = 0;
      for (const line of lines) {
        // 跳过注释和空行
        if (line.trim().startsWith('#') || line.trim() === '') {
          continue;
        }
        
        // 尝试提取键值对
        const parts = line.split('=');
        if (parts.length >= 2) {
          const key = parts[0].trim();
          if (key) {
            this.definedTranslationKeys.add(key);
            keysCount++;
          }
        }
      }
      
      logger.info('处理属性文件', { 
        文件: filePath, 
        添加键数: keysCount
      });
    } catch (error) {
      logger.warn('处理属性文件失败', { 
        文件: filePath, 
        错误: error instanceof Error ? error.message : String(error)
      });
    }
  }
  
  /**
   * 处理 JSON 资源文件
   * @param filePath 文件路径
   */
  private async processJsonResourceFile(filePath: string): Promise<void> {
    try {
      const content = await this.readJavaFile(filePath);
      try {
        const jsonData = JSON.parse(content);
        
        // 递归提取所有的键
        const extractKeys = (obj: any, prefix = '') => {
          let keysCount = 0;
          
          for (const [key, value] of Object.entries(obj)) {
            const fullKey = prefix ? `${prefix}.${key}` : key;
            
            if (typeof value === 'object' && value !== null) {
              // 递归处理嵌套对象
              keysCount += extractKeys(value, fullKey);
            } else {
              // 添加叶子节点的键
              this.definedTranslationKeys.add(fullKey);
              keysCount++;
            }
          }
          
          return keysCount;
        };
        
        const keysCount = extractKeys(jsonData);
        
        logger.info('处理JSON资源文件', { 
          文件: filePath, 
          添加键数: keysCount
        });
      } catch (parseError) {
        logger.warn('JSON解析失败', { 
          文件: filePath, 
          错误: parseError instanceof Error ? parseError.message : String(parseError)
        });
      }
    } catch (error) {
      logger.warn('处理JSON资源文件失败', { 
        文件: filePath, 
        错误: error instanceof Error ? error.message : String(error)
      });
    }
  }

  /**
   * 并行解析多个文件
   * @param filePaths 文件路径列表
   * @param task 提取任务
   * @param batchSize 批处理大小
   */
  public async parseFiles(filePaths: string[], task: ExtractionTask, batchSize = 5): Promise<ExtractionResult[]> {
    const results: ExtractionResult[] = [];
    const failedFiles: string[] = [];
    
    // 使用批处理来避免同时打开过多文件
    for (let i = 0; i < filePaths.length; i += batchSize) {
      const batch = filePaths.slice(i, i + batchSize);
      const batchPromises = batch.map(filePath => this.parseFile(filePath, task).catch(err => {
        failedFiles.push(filePath);
        logger.error('批处理中文件解析失败', {
          文件路径: filePath,
          错误信息: err instanceof Error ? err.message : String(err)
        });
        // 返回一个失败的结果
        return {
          taskId: task.taskId,
          status: 'failed' as const,
          startTime: new Date().toISOString(),
          endTime: new Date().toISOString(),
          statistics: {
            totalFiles: 1,
            processedFiles: 0,
            extractedKeys: 0,
            errors: 1,
            processingTime: 0
          },
          translations: [],
          analysis: {
            coverage: { overall: 0, byLanguage: {}, byModule: {}, missingKeys: [], redundantKeys: [] },
            usage: { highFrequency: [], lowFrequency: [], unusedKeys: [] },
            modules: {},
            quality: { duplicates: [], namingIssues: [], contextIssues: [] }
          },
          errors: [{ file: filePath, message: err instanceof Error ? err.message : String(err) }],
          suggestions: []
        };
      }));
      const batchResults = await Promise.all(batchPromises);
      results.push(...batchResults);
    }
    
    if (failedFiles.length > 0) {
      logger.warn('部分文件解析失败', { 
        总文件数: filePaths.length, 
        失败文件数: failedFiles.length,
        失败文件列表: failedFiles.slice(0, 10) // 只记录前10个失败文件
      });
    }
    
    return results;
  }

  /**
   * 解析 Java/Kotlin 文件
   * @param filePath 文件路径
   * @param task 提取任务
   */
  public async parseFile(filePath: string, task: ExtractionTask): Promise<ExtractionResult> {
    const startTime = new Date();
    let status: 'success' | 'failed' = 'success';
    let error: Error | null = null;
    let translations: TranslationInfo[] = [];
    let content = '';

    try {
      // 1. 文件检查
      await this.validateFile(filePath);
      
      // 根据文件扩展名设置对应的语言解析器
      const fileExt = path.extname(filePath).toLowerCase();
      if (fileExt === '.kt') {
        this.parser.setLanguage(Kotlin);
        // logger.info('使用 Kotlin 解析器解析文件', { 文件: filePath });
      } else {
        this.parser.setLanguage(Java);
        // logger.info('使用 Java 解析器解析文件', { 文件: filePath });
      }
      
      // 2. 使用缓存机制
      const cacheKey = `${filePath}-${task.taskId}`;
      const cachedResult = await this.getCachedResult(cacheKey);
      if (cachedResult) {
        return cachedResult;
      }

      // 3. 读取文件内容，支持多种编码
      try {
        content = await this.readJavaFile(filePath);
        
        // 检查内容是否为空，为空则跳过后续处理
        if (!content) {
          logger.warn('文件内容为空，跳过解析', { 文件: filePath });
          return {
            taskId: task.taskId,
            status: 'success',
            startTime: startTime.toISOString(),
            endTime: new Date().toISOString(),
            statistics: {
              totalFiles: 1,
              processedFiles: 1,
              extractedKeys: 0,
              errors: 0,
              processingTime: new Date().getTime() - startTime.getTime()
            },
            translations: [],
            analysis: {
              coverage: { overall: 0, byLanguage: {}, byModule: {}, missingKeys: [], redundantKeys: [] },
              usage: { highFrequency: [], lowFrequency: [], unusedKeys: [] },
              modules: {},
              quality: { duplicates: [], namingIssues: [], contextIssues: [] }
            },
            errors: [],
            suggestions: []
          };
        }
      } catch (readError) {
        logger.error('文件读取失败', { 
          文件: filePath, 
          错误: readError instanceof Error ? readError.message : String(readError) 
        });
        throw readError;
      }

      // 4. 预处理文件内容
      try {
        content = this.preprocessContent(content);
      } catch (preprocessError) {
        logger.warn('内容预处理失败', { 
          文件: filePath, 
          错误: preprocessError instanceof Error ? preprocessError.message : String(preprocessError) 
        });
        // 继续使用原始内容
      }

      // 5. 解析Java代码
      try {
        // 使用超时机制避免解析器卡死
        const parsePromise = new Promise<Parser.Tree>((resolve, reject) => {
          try {
            const tree = this.parser.parse(content);
            resolve(tree);
          } catch (parseError) {
            reject(parseError);
          }
        });

        const tree = await Promise.race([
          parsePromise,
          new Promise<never>((_, reject) => 
            setTimeout(() => reject(new Error(`Parse timeout after ${this.options.parseTimeout}ms`)), 
            this.options.parseTimeout)
          )
        ]);

        // 提取翻译文本
        translations = this.extractTranslations(tree.rootNode, filePath);
      } catch (parseError) {
        logger.warn('Tree-sitter解析失败，尝试使用正则表达式提取', { 
          文件: filePath, 
          错误: parseError instanceof Error ? parseError.message : String(parseError) 
        });
        
        // 回退到正则表达式提取
        if (this.options.fallbackToRegex) {
          translations = this.extractTranslationsWithRegex(content, filePath);
        } else {
          throw parseError;
        }
      }

      // 6. 生成统计信息
      const statistics = this.generateStatistics();
      
      // 7. 创建结果
      const result: ExtractionResult = {
        taskId: task.taskId,
        status: 'success',
        startTime: startTime.toISOString(),
        endTime: new Date().toISOString(),
        statistics: {
          totalFiles: 1,
          processedFiles: 1,
          extractedKeys: translations.length,
          errors: 0,
          processingTime: new Date().getTime() - startTime.getTime()
        },
        translations,
        analysis: {
          coverage: {
            overall: statistics.coverageRate,
            byLanguage: {},
            byModule: statistics.moduleCoverage,
            missingKeys: [],
            redundantKeys: []
          },
          usage: {
            highFrequency: [],
            lowFrequency: [],
            unusedKeys: []
          },
          modules: this.transformModuleDetails(statistics.moduleDetails),
          quality: {
            duplicates: [],
            namingIssues: [],
            contextIssues: []
          }
        },
        errors: [],
        suggestions: []
      };

      // 8. 缓存结果
      await this.cacheResult(cacheKey, result);
      
      // logger.info('Java文件解析成功', {
      //   文件路径: filePath,
      //   耗时: `${result.statistics.processingTime}ms`,
      //   翻译键数量: translations.length
      // });
      
      return result;
    } catch (error) {
      const errorResult: ExtractionResult = {
        taskId: task.taskId,
        status: 'failed',
        startTime: startTime.toISOString(),
        endTime: new Date().toISOString(),
        statistics: {
          totalFiles: 1,
          processedFiles: 0,
          extractedKeys: 0,
          errors: 1,
          processingTime: new Date().getTime() - startTime.getTime()
        },
        translations: [],
        analysis: {
          coverage: {
            overall: 0,
            byLanguage: {},
            byModule: {},
            missingKeys: [],
            redundantKeys: []
          },
          usage: {
            highFrequency: [],
            lowFrequency: [],
            unusedKeys: []
          },
          modules: {},
          quality: {
            duplicates: [],
            namingIssues: [],
            contextIssues: []
          }
        },
        errors: [{
          file: filePath,
          message: error instanceof Error ? error.message : String(error)
        }],
        suggestions: []
      };

      logger.error('Java文件解析失败', { 
        文件路径: filePath, 
        错误类型: error instanceof Error ? error.constructor.name : typeof error,
        错误信息: error instanceof Error ? error.message : String(error),
        错误堆栈: error instanceof Error ? error.stack : undefined
      });

      return errorResult;
    }
  }

  /**
   * 验证文件
   * @param filePath 文件路径
   */
  private async validateFile(filePath: string): Promise<void> {
    // 检查文件是否存在
    if (!fs.existsSync(filePath)) {
      throw new Error(`File not found: ${filePath}`);
    }

    // 检查文件类型
    const stats = fs.statSync(filePath);
    if (!stats.isFile()) {
      throw new Error(`Not a file: ${filePath}`);
    }

    // 检查文件大小
    if (stats.size > this.options.maxFileSize!) {
      throw new Error(`File too large (${stats.size} bytes), max size: ${this.options.maxFileSize} bytes`);
    }

    // 检查文件扩展名
    const fileExt = path.extname(filePath).toLowerCase();
    if (fileExt !== '.java' && fileExt !== '.kt') {
      throw new Error(`不支持的文件类型: ${filePath}，仅支持 .java 和 .kt 文件`);
    }
  }

  /**
   * 文件预处理
   * @param content 原始内容
   */
  private preprocessContent(content: string): string {
    if (!content) return '';
    
    // 1. 移除复杂的注释块
    content = content.replace(/\/\*[\s\S]*?\*\//g, '/* 注释 */');
    
    // 2. 简化行注释
    content = content.replace(/\/\/.*$/gm, '// 注释');
    
    // 3. 处理特殊字符
    content = content.replace(/[\u0000-\u0008\u000B\u000C\u000E-\u001F]/g, '');
    
    // 4. 简化大型数组或复杂初始化
    content = content.replace(/\{([^{}]{300,})\}/g, '{ /* 简化复杂初始化 */ }');
    
    // 5. 简化长方法链
    content = content.replace(/(\.\w+\([^()]*\)){5,}/g, '/* 简化方法链 */');
    
    // 6. 简化复杂泛型
    if (this.options.skipComplexStructures) {
      content = content.replace(/<(?:[^<>]|<(?:[^<>])*>){50,}>/g, '</*简化泛型*/>');
    }
    
    // 7. 替换非ASCII引号
    content = content.replace(/[\u2018\u2019\u201C\u201D]/g, '"');
    
    return content;
  }

  /**
   * 流式读取文件并处理编码
   * @param filePath 文件路径
   */
  private async readJavaFile(filePath: string): Promise<string> {
    try {
      // 检测文件编码
      let encoding = this.options.encoding;
      
      if (encoding === 'auto') {
        try {
          // 检测文件编码
          const detected = await chardet.detectFile(filePath);
          encoding = detected || 'utf8';
          // logger.info('自动检测文件编码', { 文件: filePath, 检测编码: encoding });
        } catch (error) {
          logger.warn('编码检测失败，使用默认编码', { 文件: filePath, 默认编码: 'utf8' });
          encoding = 'utf8';
        }
      }
      
      // 检查文件是否存在
      const stats = await fs.promises.stat(filePath);
      if (stats.size === 0) {
        logger.warn('文件为空', { 文件: filePath, 大小: stats.size });
        return ''; // 返回空字符串而不是抛出错误
      }
      
      // 读取文件内容
      let content: string;
      
      try {
        // 首先尝试直接用UTF-8读取
        content = await fs.promises.readFile(filePath, 'utf8');
      } catch (utf8Error) {
        // UTF-8读取失败，尝试使用检测到的编码
        logger.warn('UTF-8读取失败，尝试使用检测到的编码', { 文件: filePath, 编码: encoding });
        
        try {
          const buffer = await fs.promises.readFile(filePath);
          content = iconv.decode(buffer, encoding || 'utf8');
        } catch (iconvError) {
          // 所有尝试都失败，使用buffer直接toString
          logger.warn('所有编码尝试失败，使用buffer.toString()', { 文件: filePath });
          const buffer = await fs.promises.readFile(filePath);
          content = buffer.toString();
        }
      }
      
      // 检查文件内容 - 改为警告而不是抛出错误
      if (!content || content.trim() === '') {
        logger.warn('文件内容为空或只有空白字符', { 文件: filePath });
        return ''; // 返回空字符串继续处理
      }
      
      // logger.info('文件读取成功', { 
      //   文件: filePath, 
      //   编码: encoding, 
      //   大小: content.length 
      // });
      
      return content;
    } catch (error) {
      logger.error('Java文件读取失败', {
        文件路径: filePath,
        错误信息: error instanceof Error ? error.message : String(error)
      });
      // 返回空字符串而不是抛出错误，让解析流程可以继续
      return '';
    }
  }

  /**
   * 使用正则表达式提取翻译文本（当AST解析失败时使用）
   * @param content 文件内容
   * @param filePath 文件路径
   */
  private extractTranslationsWithRegex(content: string, filePath: string): TranslationInfo[] {
    logger.info('使用正则表达式提取翻译', { 文件: filePath });
    const translations: TranslationInfo[] = [];
    const isKotlinFile = path.extname(filePath).toLowerCase() === '.kt';
    
    try {
      // 1. 提取字符串字面量
      let stringPatterns = [
        // 普通字符串
        /"((?:[^"\\]|\\.)*)"/g,
        // 字符字面量
        /'((?:[^'\\]|\\.)*)'/g
      ];
      
      if (isKotlinFile) {
        // 添加 Kotlin 特有的三引号字符串
        stringPatterns.push(/"""([\s\S]*?)"""/g);
        // 添加 Kotlin 的字符串模板
        stringPatterns.push(/"([^"]*?\$\{[^}]*\}[^"]*?)"/g);
        // 添加 string(R.string.xxx) 调用
        stringPatterns.push(/string\(R\.string\.(\w+)\)/g);
        // 添加 this.string 或 context.string 等调用
        stringPatterns.push(/(\w+)\.string\(R\.string\.(\w+)\)/g);
      }
      
      let lineNumber = 1;
      let lastIndex = 0;
      
      for (const pattern of stringPatterns) {
        let match;
        // 重置正则表达式的 lastIndex
        pattern.lastIndex = 0;
        
        while ((match = pattern.exec(content)) !== null) {
          const matchedText = match[0];
          const value = match[1] || (match[2] ? match[2] : matchedText);
          
          // 计算行号
          for (let i = lastIndex; i < match.index; i++) {
            if (content[i] === '\n') lineNumber++;
          }
          lastIndex = match.index;
          
          // 检查是否是翻译文本
          if (this.isTranslationText(value)) {
            // 获取周围上下文
            const lineStart = content.lastIndexOf('\n', match.index) + 1;
            const lineEnd = content.indexOf('\n', match.index);
            const lineContent = content.substring(lineStart, lineEnd > -1 ? lineEnd : undefined);
            
            // 提取类名（Kotlin 和 Java 语法不同）
            let className = '';
            if (isKotlinFile) {
              const classMatch = /\bobject\s+(\w+)|class\s+(\w+)/.exec(content.substring(0, match.index));
              className = classMatch ? (classMatch[1] || classMatch[2]) : '';
            } else {
              const classMatch = /class\s+(\w+)/.exec(content.substring(0, match.index));
              className = classMatch ? classMatch[1] : '';
            }
            
            // 提取方法名（Kotlin 和 Java 语法不同）
            let methodName = '';
            if (isKotlinFile) {
              const methodMatch = /\bfun\s+(\w+)\s*\([^)]*\)\s*(\{|=)/.exec(content.substring(0, match.index));
              methodName = methodMatch ? methodMatch[1] : '';
            } else {
              const methodMatch = /\b(\w+)\s*\([^)]*\)\s*\{[^{]*/.exec(content.substring(0, match.index));
              methodName = methodMatch ? methodMatch[1] : '';
            }
            
            // 生成唯一ID
            const id = `${filePath}:${lineNumber}:${value}`;
            
            // 获取支持的语言列表
            const supportedLanguages = this.getSupportedLanguages();
            
            translations.push({
              id,
              isKey: true,
              moduleLevel: 0,
              key: value,
              file: filePath,
              line: lineNumber,
              column: match.index - lineStart,
              context: methodName || className || '',
              module: this.getModuleFromPath(filePath),
              tags: [methodName, className].filter(Boolean),
              frequency: 1,
              node_type: isKotlinFile ? 'kotlin_string' : 'string_literal',
              attribute: '',
              element: '',
              isDefined: this.definedTranslationKeys.has(value),
              values: supportedLanguages.map(language => ({
                language,
                value: this.getTranslationValue(value, language),
                status: this.getTranslationStatus(value, language)
              }))
            });
          }
        }
      }
      
      logger.info('正则表达式提取完成', { 文件: filePath, 提取数量: translations.length });
      return translations;
    } catch (error) {
      logger.error('正则表达式提取失败', { 
        文件: filePath, 
        错误: error instanceof Error ? error.message : String(error) 
      });
      return [];
    }
  }

  /**
   * 从AST树中提取翻译文本
   * @param node AST节点
   * @param filePath 文件路径
   */
  private extractTranslations(node: any, filePath: string): TranslationInfo[] {
    const translations: TranslationInfo[] = [];
    
    // 最大递归深度限制，避免栈溢出
    const maxDepth = this.options.maxDepth || 100;
    
    // 递归遍历AST树
    const traverseWithDepthLimit = (node: any, depth = 0) => {
      if (!node || depth > maxDepth) return;
      
      // 检查递归深度
      if (depth === maxDepth) {
        logger.warn('达到最大递归深度限制', { 文件: filePath, 深度: maxDepth });
        return;
      }
      
      // 检查节点类型
      if (node.type) {
        // Kotlin 字符串处理
        if (node.type === 'string_literal' || 
            node.type === 'character_literal' || 
            node.type === 'line_string_literal' || 
            node.type === 'multi_line_string_literal') {
          this.processKotlinStringNode(node, filePath, translations);
        } 
        // Kotlin 资源调用处理
        else if (node.type === 'call_expression' && 
                node.text && 
                (node.text.includes('R.string') || node.text.includes('.string'))) {
          this.processKotlinResourceCall(node, filePath, translations);
        }
        else {
          // Java 字符串处理
          if (node.type === 'string_literal') {
            const value = node.text.slice(1, -1); // 移除引号
            // 检查是否是翻译文本
            if (this.isTranslationText(value)) {
              const context = this.getContext(node);
              const scope = this.getScope(node);
              const method = this.getTranslationMethod(node);
              
              // 生成唯一ID
              const id = `${filePath}:${node.startPosition.row + 1}:${value}`;
              
              // 获取支持的语言列表
              const supportedLanguages = this.getSupportedLanguages();
              
              translations.push({
                id,
                isKey: true,
                moduleLevel: 0,
                key: value,
                file: filePath,
                line: node.startPosition.row + 1,
                column: node.startPosition.column,
                context: context.methodName || context.className || '',
                module: this.getModuleFromPath(filePath),
                tags: this.extractTags(value, context),
                frequency: 1,
                node_type: node.type,
                attribute: this.getAttributeName(node),
                element: this.getElementName(node),
                isDefined: this.definedTranslationKeys.has(value),
                values: supportedLanguages.map(language => ({
                  language,
                  value: this.getTranslationValue(value, language),
                  status: this.getTranslationStatus(value, language)
                }))
              });
            }
          }
        }
      }
      
      // 递归处理子节点
      if (node.children && Array.isArray(node.children)) {
        for (const child of node.children) {
          traverseWithDepthLimit(child, depth + 1);
        }
      }
    };
    
    // 从根节点开始遍历
    traverseWithDepthLimit(node);
    
    return translations;
  }

  /**
   * 处理 Kotlin 字符串节点
   */
  private processKotlinStringNode(node: any, filePath: string, translations: TranslationInfo[]): void {
    try {
      // 处理普通字符串
      let value = node.text;
      
      // 移除引号
      if (value.startsWith('"') && value.endsWith('"')) {
        value = value.slice(1, -1);
      } else if (value.startsWith("'") && value.endsWith("'")) {
        value = value.slice(1, -1);
      } else if (value.startsWith('"""') && value.endsWith('"""')) {
        value = value.slice(3, -3);
      }
      
      if (this.isTranslationText(value)) {
        const context = this.getContext(node);
        
        // 生成唯一ID
        const id = `${filePath}:${node.startPosition.row + 1}:${value}`;
        
        // 获取支持的语言列表
        const supportedLanguages = this.getSupportedLanguages();
        
        translations.push({
          id,
          isKey: true,
          moduleLevel: 0,
          key: value,
          file: filePath,
          line: node.startPosition.row + 1,
          column: node.startPosition.column,
          context: context.methodName || context.className || '',
          module: this.getModuleFromPath(filePath),
          tags: this.extractTags(value, context),
          frequency: 1,
          node_type: node.type,
          attribute: this.getAttributeName(node),
          element: this.getElementName(node),
          isDefined: this.definedTranslationKeys.has(value),
          values: supportedLanguages.map(language => ({
            language,
            value: this.getTranslationValue(value, language),
            status: this.getTranslationStatus(value, language)
          }))
        });
      }
    } catch (error) {
      logger.warn('Kotlin 字符串处理错误', {
        错误: error instanceof Error ? error.message : String(error)
      });
    }
  }

  /**
   * 处理 Kotlin 资源调用
   */
  private processKotlinResourceCall(node: any, filePath: string, translations: TranslationInfo[]): void {
    try {
      const nodeText = node.text;
      let resourceKey = '';
      
      // 尝试匹配 string(R.string.xxx) 模式
      const stringMatch = nodeText.match(/string\(R\.string\.(\w+)\)/);
      if (stringMatch) {
        resourceKey = stringMatch[1];
      } 
      // 尝试匹配 xxx.string 模式
      else if (nodeText.includes('.string')) {
        resourceKey = nodeText.split('.').pop() || '';
      }
      
      if (resourceKey && this.isValidTranslationKey(resourceKey)) {
        const context = this.getContext(node);
        
        // 生成唯一ID
        const id = `${filePath}:${node.startPosition.row + 1}:${resourceKey}`;
        
        // 获取支持的语言列表
        const supportedLanguages = this.getSupportedLanguages();
        
        translations.push({
          id,
          isKey: true,
          moduleLevel: 0,
          key: resourceKey,
          file: filePath,
          line: node.startPosition.row + 1,
          column: node.startPosition.column,
          context: context.methodName || context.className || '',
          module: this.getModuleFromPath(filePath),
          tags: this.extractTags(resourceKey, context),
          frequency: 1,
          node_type: 'resource_call',
          attribute: '',
          element: '',
          isDefined: true, // 假设资源调用总是指向已定义的资源
          values: supportedLanguages.map(language => ({
            language,
            value: this.getTranslationValue(resourceKey, language),
            status: this.getTranslationStatus(resourceKey, language)
          }))
        });
      }
    } catch (error) {
      logger.warn('Kotlin 资源调用处理错误', {
        错误: error instanceof Error ? error.message : String(error)
      });
    }
  }

  /**
   * 提取标签
   * @param value 翻译文本
   * @param context 上下文
   */
  private extractTags(value: string, context: TranslationContext): string[] {
    const tags: string[] = [];
    
    // 从方法名提取标签
    if (context.methodName) {
      tags.push(context.methodName.toLowerCase());
    }
    
    // 从类名提取标签
    if (context.className) {
      tags.push(context.className.toLowerCase());
    }
    
    // 从翻译文本提取标签
    const words = value.toLowerCase().split(/[\s_]+/);
    tags.push(...words);
    
    // 去重
    return [...new Set(tags)];
  }

  /**
   * 获取属性名称
   * @param node Tree-sitter 节点
   */
  private getAttributeName(node: any): string {
    const parent = node.parent;
    if (parent && parent.type === 'attribute') {
      return parent.childForFieldName('name')?.text || '';
    }
    return '';
  }

  /**
   * 获取元素名称
   * @param node Tree-sitter 节点
   */
  private getElementName(node: any): string {
    const parent = node.parent;
    if (parent && parent.type === 'element') {
      return parent.childForFieldName('name')?.text || '';
    }
    return '';
  }

  /**
   * 判断是否是翻译文本
   * @param text 文本内容
   */
  private isTranslationText(text: string): boolean {
    if (!text) return false;
    
    // 检查是否是非翻译字符串
    if (NON_TRANSLATION_STRINGS.has(text)) {
      return false;
    }
    
    // 检查是否是 Bundle 键值前缀
    if (Array.from(BUNDLE_KEY_PREFIXES).some(prefix => 
      text.toLowerCase().startsWith(prefix.toLowerCase()))) {
      return false;
    }
    
    // 检查是否是 R.string 引用
    if (text.includes('R.string.')) {
      const match = text.match(R_STRING_PATTERN);
      if (match) {
        const key = match[1];
        return this.isValidTranslationKey(key);
      }
      return false;
    }
    
    // 检查是否是 Kotlin 风格的 string() 引用
    if (text.includes('string(R.string.')) {
      const match = text.match(/string\(R\.string\.([a-z][a-z0-9_]*(_[a-z0-9_]+)*)\)/i);
      if (match) {
        const key = match[1];
        return this.isValidTranslationKey(key);
      }
    }
    
    // 检查是否是 Kotlin 扩展函数 xxx.string 调用
    if (text.match(/\b\w+\.string\b/)) {
      return true;
    }
    
    // 检查是否是已定义的翻译键
    if (this.definedTranslationKeys.has(text)) {
      return true;
    }
    
    // 检查是否符合翻译键格式
    if (!TRANSLATION_KEY_PATTERN.test(text)) {
      return false;
    }
    
    return true;
  }

  /**
   * 验证翻译键是否有效
   * @param key 翻译键
   */
  private isValidTranslationKey(key: string): boolean {
    if (!key) return false;
    
    // 检查是否是非翻译字符串
    if (NON_TRANSLATION_STRINGS.has(key)) {
      return false;
    }
    
    // 检查是否是 Bundle 键值前缀
    if (Array.from(BUNDLE_KEY_PREFIXES).some(prefix => 
      key.toLowerCase().startsWith(prefix.toLowerCase()))) {
      return false;
    }
    
    // 检查是否符合翻译键格式
    if (!TRANSLATION_KEY_PATTERN.test(key)) {
      return false;
    }
    
    return true;
  }

  /**
   * 获取节点的上下文
   * @param node Tree-sitter 节点
   */
  private getContext(node: any): TranslationContext {
    const context: TranslationContext = {};
    
    // 判断文件类型
    const isKotlinFile = node.tree?.rootNode?.text?.endsWith('.kt') || false;
    
    if (isKotlinFile) {
      // Kotlin 上下文获取
      
      // 获取方法声明 - Kotlin 用 'fun' 关键字
      const methodNode = this.findAncestor(node, 'function_declaration');
      if (methodNode) {
        const methodNameNode = methodNode.childForFieldName('name');
        if (methodNameNode) {
          context.methodName = methodNameNode.text;
          context.methodSignature = methodNode.text;
        }
      }
      
      // 获取类声明 - Kotlin 可能是 class 或 object
      const classNode = 
        this.findAncestor(node, 'class_declaration') || 
        this.findAncestor(node, 'object_declaration');
      
      if (classNode) {
        const classNameNode = classNode.childForFieldName('name');
        if (classNameNode) {
          context.className = classNameNode.text;
          context.classType = classNode.type === 'object_declaration' ? 'object' : 'class';
        }
      }
      
      // Kotlin 特有的属性上下文
      const propertyNode = this.findAncestor(node, 'property_declaration');
      if (propertyNode) {
        const propertyNameNode = propertyNode.childForFieldName('name');
        if (propertyNameNode && !context.methodName) {
          context.methodName = propertyNameNode.text;
        }
      }
    } else {
      // Java 上下文获取
      
      // 获取所在方法
      const methodNode = this.findAncestor(node, 'method_declaration');
      if (methodNode) {
        const methodNameNode = methodNode.childForFieldName('name');
        if (methodNameNode) {
          context.methodName = methodNameNode.text;
          context.methodSignature = methodNode.text;
        }
      }
      
      // 获取所在类
      const classNode = this.findAncestor(node, 'class_declaration');
      if (classNode) {
        const classNameNode = classNode.childForFieldName('name');
        if (classNameNode) {
          context.className = classNameNode.text;
          context.classType = 'class';
        }
      }
    }
    
    // 获取语句 - 对两种语言都适用
    const statementNode = this.findAncestor(node, 'statement') || this.findAncestor(node, 'expression_statement');
    if (statementNode) {
      context.statement = statementNode.text;
    }
    
    return context;
  }

  /**
   * 获取节点的作用域
   * @param node Tree-sitter 节点
   */
  private getScope(node: any): string {
    const classNode = this.findAncestor(node, 'class_declaration');
    if (classNode) {
      const classNameNode = classNode.childForFieldName('name');
      return classNameNode ? classNameNode.text : '';
    }
    return '';
  }

  /**
   * 获取翻译方法
   * @param node Tree-sitter 节点
   */
  private getTranslationMethod(node: any): string {
    // 查找方法调用节点
    const methodCall = this.findAncestor(node, 'method_invocation');
    if (!methodCall) return '';
    
    const methodNameNode = methodCall.childForFieldName('name');
    if (!methodNameNode) return '';
    
    const methodName = methodNameNode.text;
    const fullMethodCall = methodCall.text;
    
    // 查找匹配的翻译方法
    const method = TRANSLATION_METHODS.find(m => 
      m.name === methodName || fullMethodCall.includes(m.fullName)
    );
    
    if (method) {
      // 更新方法使用统计
      this.methodUsage.set(method.fullName, (this.methodUsage.get(method.fullName) || 0) + 1);
      return method.fullName;
    }
    
    return '';
  }

  /**
   * 查找祖先节点
   * @param node 当前节点
   * @param type 节点类型
   */
  private findAncestor(node: any, type: string): any {
    let current = node;
    while (current && current.parent) {
      if (current.type === type) {
        return current;
      }
      current = current.parent;
    }
    return null;
  }

  /**
   * 从文件路径获取模块信息
   * @param filePath 文件路径
   */
  private getModuleFromPath(filePath: string): string {
    try {
      const pathParts = filePath.split(path.sep);
      const moduleParts: string[] = [];
      
      // 处理特殊的资源目录
      if (filePath.includes('res-')) {
        const parts = filePath.split('res-');
        if (parts.length > 1) {
          const resType = parts[1].split(path.sep)[0];
          return resType;
        }
      }
      
      // 从包名推断模块
      if (filePath.includes('/src/main/java/')) {
        const parts = filePath.split('/src/main/java/');
        if (parts.length > 1 && parts[1]) {
          const packageParts = parts[1].split('/');
          if (packageParts.length >= 3) {
            for (let i = 2; i < packageParts.length - 1; i++) {
              const part = packageParts[i];
              if (!this.isCommonPackageName(part)) {
                moduleParts.push(part);
              }
            }
          }
        }
      }
      
      // 从资源目录结构推断模块
      if (filePath.includes('/res/')) {
        let foundRes = false;
        for (let i = 0; i < pathParts.length; i++) {
          const part = pathParts[i];
          if (part === 'res') {
            foundRes = true;
            // 向上查找模块名
            for (let j = i - 1; j >= 0; j--) {
              const candidate = pathParts[j];
              if (!this.isCommonDirectoryName(candidate)) {
                moduleParts.unshift(candidate);
                break;
              }
            }
            break;
          } else if (!foundRes && !this.isCommonDirectoryName(part)) {
            moduleParts.push(part);
          }
        }
      }
      
      // 从目录结构推断模块
      if (moduleParts.length === 0) {
        for (const part of pathParts) {
          if (!this.isCommonDirectoryName(part) && 
              !part.endsWith('.java') && 
              !part.endsWith('.kt') && 
              !part.endsWith('.xml')) {
            moduleParts.push(part);
          }
        }
      }
      
      return moduleParts.length > 0 ? moduleParts.join('.') : 'app';
    } catch (error) {
      logger.warn('模块推断失败', { 
        文件路径: filePath, 
        错误: error instanceof Error ? error.message : String(error) 
      });
      return 'unknown';
    }
  }

  /**
   * 检查是否是常见的包名
   * @param name 包名
   */
  private isCommonPackageName(name: string): boolean {
    const commonNames = [
      'com', 'org', 'net', 'io', 'android', 'androidx', 'google', 'java', 'javax', 'kotlin',
      'app', 'src', 'main', 'test', 'utils', 'util', 'helper', 'helpers', 'common', 'base',
      'core', 'impl', 'internal', 'model', 'entity', 'dto', 'dao', 'service', 'services',
      'repository', 'repositories', 'manager', 'managers', 'provider', 'providers',
      'controller', 'controllers', 'view', 'views', 'activity', 'activities',
      'fragment', 'fragments', 'adapter', 'adapters', 'listener', 'listeners',
      'callback', 'callbacks', 'handler', 'handlers'
    ];
    return commonNames.includes(name);
  }

  /**
   * 检查是否是常见的目录名
   * @param name 目录名
   */
  private isCommonDirectoryName(name: string): boolean {
    const commonNames = [
      'src', 'main', 'test', 'debug', 'release', 'java', 'kotlin', 'res', 'resources',
      'assets', 'libs', 'build', 'gradle', 'app', 'lib', 'module', 'common', 'base',
      'core', 'utils', 'test', 'demo', 'example', 'sample', 'layout', 'drawable',
      'values', 'anim', 'color', 'menu', 'raw', 'xml', 'font', 'mipmap'
    ];
    return commonNames.includes(name) || 
           name.startsWith('v') || 
           name.startsWith('api') || 
           name.startsWith('android-') ||
           name === '' ||
           name.startsWith('.') ||
           name === 'build' ||
           name === 'generated';
  }

  /**
   * 生成统计信息
   */
  private generateStatistics(): TranslationStatistics {
    const totalKeys = this.definedTranslationKeys.size;
    const coveredKeys = this.usedTranslationKeys.size;
    const duplicateKeys = this.processedReferences.size - this.usedTranslationKeys.size;
    
    const statistics: TranslationStatistics = {
      totalKeys,
      coveredKeys,
      duplicateKeys,
      invalidKeys: 0,
      coverageRate: totalKeys > 0 ? coveredKeys / totalKeys : 0,
      modules: {},
      moduleCoverage: {},
      moduleDetails: {},
      methodUsage: {}
    };
    
    // 模块统计
    this.moduleMap.forEach((keys, module) => {
      statistics.modules[module] = keys.size;
      statistics.moduleCoverage[module] = totalKeys > 0 ? keys.size / totalKeys : 0;
      
      statistics.moduleDetails[module] = {
        total: keys.size,
        covered: keys.size,
        invalid: 0,
        duplicate: 0
      };
    });
    
    // 方法使用统计
    this.methodUsage.forEach((count, method) => {
      statistics.methodUsage[method] = count;
    });
    
    return statistics;
  }

  /**
   * 保存解析结果到文件
   * @param results 解析结果数组
   * @param exportPath 导出路径
   * @param callback 可选的回调函数，用于在保存完成后通知调用方
   */
  public async saveResults(
    results: ExtractionResult[], 
    exportPath: string,
    callback?: (mergedResult: ExtractionResult) => void
  ): Promise<void> {
    try {
      // 确保导出目录存在 - 使用同步方法
      const exportDir = path.dirname(exportPath);
      if (!fs.existsSync(exportDir)) {
        logger.info(`创建导出目录: ${exportDir}`);
        fs.mkdirSync(exportDir, { recursive: true });
      }

      // 合并所有结果
      const mergedResult = this.mergeResults(results);

      // 格式化 JSON 数据
      const jsonData = JSON.stringify(mergedResult, null, 2);

      // 写入文件
      await fs.promises.writeFile(exportPath, jsonData, 'utf-8');

      logger.info('解析结果已保存', {
        导出路径: exportPath,
        文件数量: results.length,
        总翻译键数: mergedResult.translations.length
      });
      
      // 添加明确的解析完成日志，包含时间戳
      const completionTime = new Date().toISOString();
      logger.info('解析完成', {
        时间戳: completionTime,
        总键数: mergedResult.translations.length,
        总文件数: results.length,
        状态: 'SUCCESS'
      });
      
      // 触发parseCompleted事件
      this.emit('parseCompleted', {
        result: mergedResult,
        exportPath: exportPath,
        completionTime: completionTime
      });
      
      // 如果提供了回调函数，则调用它
      if (callback && typeof callback === 'function') {
        callback(mergedResult);
      }
    } catch (error) {
      logger.error('保存解析结果失败', {
        导出路径: exportPath,
        错误信息: error instanceof Error ? error.message : String(error)
      });
      
      // 触发parseError事件
      this.emit('parseError', {
        error: error,
        exportPath: exportPath
      });
      
      throw error;
    }
  }

  /**
   * 合并多个解析结果
   * @param results 解析结果数组
   */
  private mergeResults(results: ExtractionResult[]): ExtractionResult {
    const mergedResult: ExtractionResult = {
      taskId: results[0]?.taskId || '',
      status: 'success',
      startTime: results[0]?.startTime || new Date().toISOString(),
      endTime: new Date().toISOString(),
      statistics: {
        totalFiles: 0,
        processedFiles: 0,
        extractedKeys: 0,
        errors: 0,
        processingTime: 0
      },
      translations: [],
      analysis: {
        coverage: {
          overall: 0,
          byLanguage: {},
          byModule: {},
          missingKeys: [],
          redundantKeys: []
        },
        usage: {
          highFrequency: [],
          lowFrequency: [],
          unusedKeys: []
        },
        modules: {},
        quality: {
          duplicates: [],
          namingIssues: [],
          contextIssues: []
        }
      },
      errors: [],
      suggestions: []
    };

    // 合并翻译文本
    const translationsMap = new Map<string, Translation>();
    
    results.forEach(result => {
      result.translations.forEach(translation => {
        const existing = translationsMap.get(translation.key);
        if (!existing) {
          translationsMap.set(translation.key, translation);
        } else {
          // 更新使用频率
          existing.frequency += translation.frequency;
          // 合并标签
          existing.tags = [...new Set([...existing.tags, ...translation.tags])];
          // 合并翻译内容
          existing.values = this.mergeTranslationValues(
            existing.values,
            translation.values
          );
        }
      });
    });

    // 转换回数组
    mergedResult.translations = Array.from(translationsMap.values());
    
    // 更新统计信息
    mergedResult.statistics.extractedKeys = mergedResult.translations.length;

    // 合并分析信息
    this.mergeAnalysis(results, mergedResult);

    return mergedResult;
  }

  /**
   * 合并翻译内容
   * @param existingTranslations 现有翻译
   * @param newTranslations 新翻译
   */
  private mergeTranslationValues(
    existingTranslations: Array<{ language: string; value: string; status: 'valid' | 'invalid' | 'missing' }>,
    newTranslations: Array<{ language: string; value: string; status: 'valid' | 'invalid' | 'missing' }>
  ): Array<{ language: string; value: string; status: 'valid' | 'invalid' | 'missing' }> {
    const merged = new Map<string, { language: string; value: string; status: 'valid' | 'invalid' | 'missing' }>();
    
    // 添加现有翻译
    existingTranslations.forEach(t => merged.set(t.language, t));
    
    // 添加或更新新翻译
    newTranslations.forEach(t => {
      const existing = merged.get(t.language);
      if (!existing || existing.status === 'missing') {
        merged.set(t.language, t);
      }
    });
    
    return Array.from(merged.values());
  }

  /**
   * 合并分析信息
   * @param results 解析结果数组
   * @param mergedResult 合并后的结果
   */
  private mergeAnalysis(results: ExtractionResult[], mergedResult: ExtractionResult): void {
    // 合并模块信息
    results.forEach(result => {
      Object.entries(result.analysis.modules).forEach(([module, info]) => {
        if (!mergedResult.analysis.modules[module]) {
          mergedResult.analysis.modules[module] = info;
        } else {
          mergedResult.analysis.modules[module].keyCount += info.keyCount;
          mergedResult.analysis.modules[module].usageFrequency = 
            (mergedResult.analysis.modules[module].usageFrequency + info.usageFrequency) / 2;
          mergedResult.analysis.modules[module].coverage = 
            (mergedResult.analysis.modules[module].coverage + info.coverage) / 2;
        }
      });
    });

    // 收集所有定义的键和使用的键
    this.collectTranslationKeys(mergedResult);

    // 计算总体覆盖率
    const totalKeys = mergedResult.translations.length;
    const coveredKeys = mergedResult.translations.filter(t => t.isDefined).length;
    mergedResult.analysis.coverage.overall = totalKeys > 0 ? coveredKeys / totalKeys : 0;

    // 更新缺失和冗余的键
    this.updateMissingAndRedundantKeys(mergedResult);

    // 更新使用频率分析
    this.updateUsageAnalysis(mergedResult);

    // 合并错误信息
    mergedResult.errors = results.flatMap(r => r.errors);

    // 合并建议
    mergedResult.suggestions = results.flatMap(r => r.suggestions);
  }

  /**
   * 收集所有定义的键和使用的键
   * @param result 解析结果
   */
  private collectTranslationKeys(result: ExtractionResult): void {
    // 从译文中提取已定义和已使用的键
    result.translations.forEach(translation => {
      // 检查是否有任何有效翻译
      const hasValidTranslation = translation.values.some(t => t.status === 'valid');
      
      if (hasValidTranslation) {
        // 如果有有效翻译，将其视为已定义
        this.definedTranslationKeys.add(translation.key);
        translation.isDefined = true;
      }
      
      // 添加到已使用的键集合
      if (translation.frequency > 0) {
        this.usedTranslationKeys.add(translation.key);
      }
    });
    
    logger.info('收集翻译键完成', { 
      已定义键数量: this.definedTranslationKeys.size,
      已使用键数量: this.usedTranslationKeys.size
    });
  }

  /**
   * 更新缺失和冗余的键
   * @param result 解析结果
   */
  private updateMissingAndRedundantKeys(result: ExtractionResult): void {
    // 清空现有的缺失和冗余键列表
    result.analysis.coverage.missingKeys = [];
    result.analysis.coverage.redundantKeys = [];
    
    // 检查每个翻译键
    result.translations.forEach(translation => {
      // 缺失的键：没有有效翻译的键
      const hasValidTranslation = translation.values.some(t => t.status === 'valid');
      if (!hasValidTranslation) {
        result.analysis.coverage.missingKeys.push(translation.key);
      }
      
      // 冗余的键：定义了但未使用的键
      if (translation.isDefined && translation.frequency === 0) {
        result.analysis.coverage.redundantKeys.push(translation.key);
      }
    });
    
    logger.info('更新缺失和冗余键完成', { 
      缺失键数量: result.analysis.coverage.missingKeys.length,
      冗余键数量: result.analysis.coverage.redundantKeys.length
    });
  }

  /**
   * 更新使用频率分析
   * @param result 解析结果
   */
  private updateUsageAnalysis(result: ExtractionResult): void {
    // 清空现有的高频、低频和未使用的键
    result.analysis.usage.highFrequency = [];
    result.analysis.usage.lowFrequency = [];
    result.analysis.usage.unusedKeys = [];
    
    // 计算使用频率统计
    const frequencies = result.translations.map(t => t.frequency);
    const totalFrequency = frequencies.reduce((sum, freq) => sum + freq, 0);
    const avgFrequency = totalFrequency / frequencies.length || 0;
    
    // 确定高频和低频阈值
    const highThreshold = Math.max(avgFrequency * 1.5, 5); // 至少需要5次使用才算高频
    const lowThreshold = Math.min(avgFrequency * 0.5, 2);  // 最多2次使用算低频
    
    // 分类翻译键
    result.translations.forEach(translation => {
      const { key, frequency } = translation;
      
      if (frequency === 0) {
        result.analysis.usage.unusedKeys.push(key);
      } else if (frequency >= highThreshold) {
        result.analysis.usage.highFrequency.push(key);
      } else if (frequency <= lowThreshold && frequency > 0) {
        result.analysis.usage.lowFrequency.push(key);
      }
    });
    
    logger.info('更新使用频率分析完成', { 
      // 高频键数量: result.analysis.usage.highFrequency.length,
      // 低频键数量: result.analysis.usage.lowFrequency.length,
      未使用键数量: result.analysis.usage.unusedKeys.length,
      平均使用频率: avgFrequency.toFixed(2)
    });
  }

  /**
   * 获取缓存结果
   * @param key 缓存键
   */
  private async getCachedResult(key: string): Promise<ExtractionResult | null> {
    // TODO: 实现缓存逻辑
    return null;
  }

  /**
   * 缓存结果
   * @param key 缓存键
   * @param result 解析结果
   */
  private async cacheResult(key: string, result: ExtractionResult): Promise<void> {
    // TODO: 实现缓存逻辑
  }

  /**
   * 转换模块详情为分析所需格式
   * @param moduleDetails 模块详情
   */
  private transformModuleDetails(moduleDetails: Record<string, { total: number; covered: number; invalid: number; duplicate: number; }>): 
    Record<string, { keyCount: number; usageFrequency: number; coverage: number; }> {
    const result: Record<string, { keyCount: number; usageFrequency: number; coverage: number; }> = {};
    
    Object.entries(moduleDetails).forEach(([module, details]) => {
      result[module] = {
        keyCount: details.total,
        usageFrequency: details.total > 0 ? details.covered / details.total : 0,
        coverage: details.total > 0 ? details.covered / details.total : 0
      };
    });
    
    return result;
  }

  /**
   * 设置语言包加载器
   * @param loader 语言包加载器实例
   */
  public setTranslationLoader(loader: TranslationPackLoader): void {
    this.translationPackLoader = loader;
    logger.info('JavaParser: 语言包加载器已设置');
  }
  
  /**
   * 获取翻译值
   * @param key 翻译键
   * @param language 语言代码
   * @returns 翻译值，如果未找到则返回键名
   */
  private getTranslationValue(key: string, language: string): string {
    if (!this.translationPackLoader) {
      return key; // 未设置语言包加载器，返回原始键名
    }
    
    return this.translationPackLoader.getTranslation(language, key) || key;
  }
  
  /**
   * 获取翻译状态
   * @param key 翻译键
   * @param language 语言代码
   * @returns 翻译状态
   */
  private getTranslationStatus(key: string, language: string): 'valid' | 'missing' {
    if (!this.translationPackLoader) {
      return 'valid'; // 未设置语言包加载器，默认为有效
    }
    
    return this.translationPackLoader.hasTranslation(language, key) ? 'valid' : 'missing';
  }
  
  /**
   * 获取支持的语言列表
   * @returns 语言代码数组，如果未设置语言包加载器则返回默认语言
   */
  private getSupportedLanguages(): string[] {
    if (!this.translationPackLoader) {
      return ['en', 'zh-CN', 'Indonesian', 'Spanish', 'Vietnamese', 'Portuguese'];
    }
    
    const languages = this.translationPackLoader.getSupportedLanguages();
    return languages.length > 0 ? languages : ['en', 'zh-CN', 'Indonesian', 'Spanish', 'Vietnamese', 'Portuguese'];
  }
} 